package org.mspring.search.task;

import java.util.List;
import java.util.Map;

import org.hibernate.Query;
import org.hibernate.Session;
import org.hibernate.SessionFactory;
import org.mspring.platform.dao.hibernate.HibernateUtils;
import org.mspring.platform.task.AbstractTask;
import org.mspring.platform.utils.StringUtils;
import org.mspring.search.Searchable;
import org.mspring.search.engine.SearchEngine;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

/**
 * 重建索引
 * 
 * @author Gao Youbo
 * @since 2013年8月1日
 */
@Component
public class LuceneIndexRebuilderTask extends AbstractTask {

    @Autowired
    private SessionFactory sessionFactory;
    @Autowired
    private SearchEngine searchEngine;

    @SuppressWarnings("unchecked")
    @Override
    protected void doTask(Map<Object, Object> paramMap) throws Exception {

        if (paramMap == null) {
            return;
        }
        Object sql = paramMap.get("sql");
        Object countSql = paramMap.get("countSql");
        Object clazz = paramMap.get("clazz");
        Object batch = paramMap.get("batch");
        if (clazz == null || batch == null) {
            return;
        }
        Class<Searchable> c = (Class<Searchable>) clazz;
        int b = Integer.parseInt(batch.toString());

        if (sql == null || StringUtils.isBlank(sql.toString())) {
            sql = "select t from " + c.getName() + " t";
        }
        if (countSql == null || StringUtils.isBlank(countSql.toString())) {
            countSql = "select count(*) from " + c.getName() + " t";
        }

        Long count = count(countSql.toString());
        build(sql.toString(), 0, b, count);
    }

    @SuppressWarnings("unchecked")
    private void build(String sql, int first, int batch, Long count) {
        Session session = HibernateUtils.getSession(sessionFactory);
        Query query = session.createQuery(sql);
        query.setFirstResult(first);
        query.setMaxResults(batch);
        List<Searchable> list = query.list();
        try {
            searchEngine.doIndex(list);
        } catch (Exception e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
        if (list.size() > 0) {
            first = first + batch;
            build(sql, first, batch, count);
        }
    }

    private Long count(String countSql) {
        Session session = HibernateUtils.getSession(sessionFactory);
        Object obj = session.createQuery(countSql).uniqueResult();
        return new Long(obj.toString());
    }

}
